#include"Channel.h"

Channel::Channel(EventLoop *loop, int fd):loop_(loop),fd_(fd)
{
}

Channel::~Channel()
{
    // 不能在析构函数中销户 ep_、fd。因为这两个东西不属于Channel类，Channel类只是对它们进行了使用上的封装。
}

int Channel::fd()
{
    return fd_;
}

void Channel::setet()
{
    events_ |= EPOLLET;
}

void Channel::enablereading()
{
    events_ |= EPOLLIN;
    loop_->ep()->updateChannel(this);
}

void Channel::disablereading()
{
    events_ &= ~EPOLLIN;
    loop_->ep()->updateChannel(this);
}

void Channel::enablewriting()
{
    events_ |= EPOLLOUT;
    loop_->ep()->updateChannel(this);
}

void Channel::disablewriting()
{
    events_ &= ~EPOLLOUT;
    loop_->ep()->updateChannel(this);
}

void Channel::disableall()
{
    events_ = 0;
    loop_->ep()->updateChannel(this);
}

void Channel::remove()
{
    // 先取消全部的事件监听-当然也可以不写这行，因为马上就要删除了
    disableall();
    loop_->ep()->removeChannel(this);
}

void Channel::setinepoll()
{
    inepoll_ = true;
}

void Channel::setrevents(uint32_t ev)
{
    revents_ = ev;
}

bool Channel::inpoll()
{
    return inepoll_;
}

uint32_t Channel::events()
{
    return events_;
}

uint32_t Channel::revents()
{
    return revents_;
}

void Channel::handleevent()
{
    // 客户端关闭事件【有些操作系统可能检测不到该事件，此时只能在EPOLLIN中，判断recv返回0，代表客户端关闭】
    if(revents_ & EPOLLRDHUP)
    {
        closecallback_();
    }
    // 读事件                 普通数据 | 带外数据【但网络编程中一般不会使用带外数据，故写不写都行】
    else if(revents_ & (EPOLLIN | EPOLLPRI))
    {
        // 回调处理
        readcallback_();
    }
    // 写事件
    else if(revents_ & EPOLLOUT)
    {
        // 回调处理写事件
        writecallback_();
    }
    // 目前没有做其他情况的判断，那么都视为错误
    else
    {
        errorcallback_();
    }
}

void Channel::setreadcallback(std::function<void()> fn)
{
    readcallback_ = fn;
}

void Channel::setclosecallback(std::function<void()> fn)
{
    closecallback_ = fn;
}

void Channel::seterrorcallback(std::function<void()> fn)
{
    errorcallback_ = fn;
}

void Channel::setwritecallback(std::function<void()> fn)
{
    writecallback_ = fn;
}
